package com.tomecode.tools.maven.settings.gui.tabs;

import java.awt.BorderLayout;
import java.awt.Color;
import java.awt.Dimension;
import java.awt.event.ActionEvent;
import java.awt.event.ActionListener;
import java.awt.event.KeyAdapter;
import java.awt.event.KeyEvent;
import java.awt.event.MouseAdapter;
import java.awt.event.MouseEvent;
import java.util.List;

import javax.swing.AbstractListModel;
import javax.swing.JLabel;
import javax.swing.JList;
import javax.swing.JPanel;
import javax.swing.JScrollPane;
import javax.swing.JTextField;
import javax.swing.ListSelectionModel;
import javax.swing.border.EmptyBorder;

import com.tomecode.tools.maven.settings.RepositoryFactory;
import com.tomecode.tools.maven.settings.gui.FrmListOfPluginGroups;
import com.tomecode.tools.maven.settings.gui.FrmLoading;
import com.tomecode.tools.maven.settings.model.Settings;
import com.tomecode.util.gui.HideNotifiListener;
import com.tomecode.util.gui.PanelFactory;
import com.tomecode.util.gui.component.Button;

/**
 * Tab for edit PluginsGoup
 * 
 * @author Frastia Tomas
 * 
 */
public final class PluginGroupsTab extends JPanel {

	private static final long serialVersionUID = 4143093656759969181L;

	private final JList pluginsGroupList;
	private final PluginsGroupModel pluginsGroupListModel;

	private final JTextField txtPluginGroup;

	private final JLabel labExistPlugin;

	private final Button bFind;

	private final Button bDelete;
	private final Button bEdit;
	private final Button bSave;

	public PluginGroupsTab(final Settings settings) {
		super(new BorderLayout());
		setBorder(new EmptyBorder(10, 10, 0, 10));

		labExistPlugin = new JLabel(" ");
		labExistPlugin.setForeground(Color.red);

		pluginsGroupListModel = new PluginsGroupModel(settings);
		pluginsGroupList = new JList(pluginsGroupListModel);
		pluginsGroupList.setSelectionMode(ListSelectionModel.SINGLE_SELECTION);
		pluginsGroupList.addMouseListener(new MouseAdapter() {
			public final void mouseClicked(MouseEvent e) {
				selectInList(pluginsGroupList.getSelectedIndex());
			}
		});
		pluginsGroupList.addKeyListener(new KeyAdapter() {
			public final void keyReleased(KeyEvent e) {
				selectInList(pluginsGroupList.getSelectedIndex());
			}
		});

		txtPluginGroup = new JTextField();
		txtPluginGroup.addKeyListener(new KeyAdapter() {
			public final void keyReleased(KeyEvent e) {
				if (txtPluginGroup.getText().trim().length() == 0) {
					labExistPlugin.setText(" ");
					bSave.setEnabled(false);
				} else if (pluginsGroupListModel.exist(txtPluginGroup.getText().trim())) {
					labExistPlugin.setText("already exists in list");
					bSave.setEnabled(false);
				} else {
					labExistPlugin.setText(" ");
					bSave.setEnabled(true);
				}
			}
		});

		bFind = new Button("...", true, new ActionListener() {
			public final void actionPerformed(ActionEvent e) {
				loadPluginGroups(settings.getPluginGroups(), settings.getRepository());
			}
		});
		bFind.setPreferredSize(new Dimension(30, 19));

		bDelete = new Button("Delete", false, new ActionListener() {
			public final void actionPerformed(ActionEvent e) {
				if (pluginsGroupList.getSelectedIndex() == -1) {
					return;
				}
				pluginsGroupListModel.remove(pluginsGroupList.getSelectedIndex());
				pluginsGroupList.updateUI();
				cleanTxts();
			}

		});
		bEdit = new Button("Edit", false, new ActionListener() {
			public final void actionPerformed(ActionEvent e) {
				if (pluginsGroupList.getSelectedIndex() == -1) {
					return;
				}
				pluginsGroupListModel.update(pluginsGroupList.getSelectedIndex(), txtPluginGroup.getText());
				pluginsGroupList.updateUI();
				cleanTxts();
			}
		});
		bSave = new Button("Save", false, new ActionListener() {
			public final void actionPerformed(ActionEvent e) {
				if (!pluginsGroupListModel.exist(txtPluginGroup.getText())) {
					pluginsGroupListModel.add(txtPluginGroup.getText());
					pluginsGroupList.updateUI();
					labExistPlugin.setText(" ");
					cleanTxts();
				} else {
					labExistPlugin.setText("already exists in list");
					bSave.setEnabled(false);
				}
			}
		});

		JPanel pWrapTxt = PanelFactory.createBorderLayout(0, 0, 0, 0);
		pWrapTxt.add(PanelFactory.wrapWithLabelNorm("Plugin goupe:", txtPluginGroup, 10), BorderLayout.CENTER);
		pWrapTxt.add(PanelFactory.wrapByBorderLayout(bFind, BorderLayout.NORTH), BorderLayout.EAST);
		pWrapTxt.add(labExistPlugin, BorderLayout.SOUTH);

		JPanel pWrapTab = PanelFactory.createBorderLayout(0, 0, 0, 0);
		pWrapTab.add(pWrapTxt, BorderLayout.CENTER);
		pWrapTab.add(PanelFactory.createButtonsPanel(bSave, bEdit, bDelete), BorderLayout.SOUTH);

		add(new JScrollPane(pluginsGroupList), BorderLayout.CENTER);

		add(pWrapTab, BorderLayout.SOUTH);
	}

	/**
	 * show {@link FrmListOfPluginGroups}
	 * 
	 * @param pluginGroups
	 * @param repository
	 */
	private final void loadPluginGroups(final List<String> pluginGroups, final java.io.File repository) {
		new Thread(new Runnable() {
			public void run() {
				FrmLoading frmLoading = new FrmLoading("Loading plugin groups...");
				frmLoading.showFrm(null);

				// load all plugin groups in local repository
				final List<String> allPluginGroups = RepositoryFactory.getPluginGroups(repository);
				frmLoading.hideMe();

				if (frmLoading.isCanceled()) {
					return;
				}

				FrmListOfPluginGroups.showMe(pluginGroups, allPluginGroups, new HideNotifiListener() {
					public final void hideForm(Object returnObj) {
						if (returnObj != null) {
							pluginsGroupListModel.add(returnObj.toString());
							pluginsGroupList.updateUI();
						}
					}
				});

			}
		}).start();
	}

	private final void selectInList(int selectedIndex) {
		if (selectedIndex == -1) {
			cleanTxts();
			return;
		}

		txtPluginGroup.setText(pluginsGroupListModel.get(selectedIndex));
		bDelete.setEnabled(true);
		bEdit.setEnabled(true);
		bSave.setEnabled(true);
	}

	private final void cleanTxts() {
		txtPluginGroup.setText("");
		bDelete.setEnabled(false);
		bEdit.setEnabled(false);
		bSave.setEnabled(false);
	}

	/**
	 * 
	 * plugins groupe model
	 * 
	 * @author Frastia Tomas
	 * 
	 */
	private final class PluginsGroupModel extends AbstractListModel {

		private static final long serialVersionUID = 8883004558971234311L;

		private final Settings settings;

		private PluginsGroupModel(Settings settings) {
			this.settings = settings;
		}

		private final boolean exist(String text) {
			return settings.getPluginGroups().contains(text);
		}

		private final void add(String text) {
			settings.addPluginGroups(text);
		}

		private final void update(int selectedIndex, String pluginGroupe) {
			settings.getPluginGroups().set(selectedIndex, pluginGroupe);
		}

		private final String get(int selectedIndex) {
			return settings.getPluginGroups().get(selectedIndex);
		}

		private final void remove(int selectedIndex) {
			settings.getPluginGroups().remove(selectedIndex);
		}

		public final Object getElementAt(int index) {
			return settings.getPluginGroups().get(index);
		}

		public final int getSize() {
			return settings.getPluginGroups().size();
		}

	}
}
